const response = require("../utils/response");
const router = require("koa-router")();
const XLSX = require("xlsx");
const {
    handleDatabaseError,
    dealNotEmpty,
    dealNotEmptyArry,
    buildRangeQuery,
    paginate,
} = require("../utils/dberrordeal");
const dayjs = require("dayjs");
const { easyCopy } = require("../utils/utils");
const { supplier } = require("../models/supplier");
const Joi = require("joi");
const validationMiddleware = require("../middleware/validate");
router.prefix('/supplier')
const rulesSchema = {
    "/supplier/addSupBill": Joi.object({
        product: Joi.array() // 数组
            .items(
                Joi.object({
                    pid: Joi.string().required(),
                    number: Joi.number().required(),
                    price: dealNotEmptyArry("产品价格"),
                    specification: dealNotEmptyArry("产品规格")
                }) // 每个对象的验证规则
            ) // 数组的验证规则
            .required(), // 数组是必需的,
        supplierInvoice: dealNotEmpty("开票情况"),
        supplierunpaid: Joi.number().min(0).required().messages({
            "number.base": "未结货款必须是数字",
            "number.min": "未结货款必须大于0",
            "any.required": "未结货款是必需的",
        }),
        supplierAmount: Joi.number().min(1).required().messages({
            "number.base": "货款总额必须是数字",
            "number.min": "货款总额必须大于0",
            "any.required": "货款总额是必需的",
        }),
        supplierName: dealNotEmpty("客户名称"),
        // phone: dealNotEmpty("联系方式"),
        supplierOrigin: dealNotEmptyArry("账单来源"),
    }),
    "/supplier/delSupBill": Joi.object({
        id: dealNotEmpty("账单id"),
    }),
    "/supplier/putSupBill": Joi.object({
        product: Joi.array() // 数组
            .items(
                Joi.object({
                    pid: Joi.string().required(),
                    number: Joi.number().required(),
                    price: dealNotEmptyArry("产品价格"),
                    specification: dealNotEmptyArry("产品规格")
                }) // 每个对象的验证规则
            ) // 数组的验证规则
            .required(), // 数组是必需的,
        id: dealNotEmpty("账单id"),
        supplierInvoice: dealNotEmpty("开票情况"),
        supplierunpaid: Joi.number().min(0).required().messages({
            "number.base": "未结货款必须是数字",
            "number.min": "未结货款必须大于0",
            "any.required": "未结货款是必需的",
        }),
        supplierAmount: Joi.number().min(1).required().messages({
            "number.base": "货款总额必须是数字",
            "number.min": "货款总额必须大于0",
            "any.required": "货款总额是必需的",
        }),
        supplierName: dealNotEmpty("客户名称"),
        // phone: dealNotEmpty("联系方式"),
        supplierOrigin: dealNotEmptyArry("账单来源"),
    }),
    "/supplier/getSupBill": Joi.object({
        id: dealNotEmpty("账单id"),
    }),
};


router.post("/getSupBillList", async (ctx, next) => {
    let data = ctx.request.body;
    let params = ctx.request.query;
    // 动态构建查询条件
    let query = {};
    query.supplierDate = data.ShippingDate
        ? buildRangeQuery(data.ShippingDate[0], data.ShippingDate[1], "time")
        : undefined;
    if (data.product)
        query.product = {
            $elemMatch: {
                pid: data.product,
            }, // 精准匹配产品名称
        };
    if (data.supplierName) query.supplierName = { $regex: data.supplierName, $options: "i" }; // 模糊查询客户名称
    if (data.supplierCode) query.supplierCode = { $regex: data.supplierCode, $options: "i" }; // 模糊查询物料
    query.supplierAmount = buildRangeQuery(+data.supplierAmountMin, +data.supplierAmountMax);
    if ([true, false].includes(data.isPayOff)) {
        query.supplierunpaid = data.isPayOff ? 0 : { $gt: 0 }
    }

    // 移除未定义的查询条件
    Object.keys(query).forEach(
        (key) => query[key] === undefined && delete query[key]
    );


    try {
        let supBills = await paginate(supplier, query, params, [
            {
                path: 'product',
                populate: {
                    path: 'pid',
                    model: 'supplierProduct' // 假设 pid 引用的是 supplierProduct 模型
                }
            },
            {
                path: 'supplierOrigin',
                model: 'bill'
            },

        ],  { createTime: -1 });
        response.success(ctx, {
            data: {
                list: supBills.results,
                total: supBills.total,
            },
        });
    } catch (err) {
        handleDatabaseError(ctx, err);
    }
});

router.post("/getTotalAmount", async (ctx, next) => {
    let data = ctx.request.body;
    let params = ctx.request.query;
    // 动态构建查询条件
    let query = {};
    query.supplierDate = data.ShippingDate
        ? buildRangeQuery(data.ShippingDate[0], data.ShippingDate[1], "time")
        : undefined;
    if (data.product)
        query.product = {
            $elemMatch: {
                pid: data.product,
            }, // 精准匹配产品名称
        };
    if (data.supplierName) query.supplierName = { $regex: data.supplierName, $options: "i" }; // 模糊查询客户名称
    if (data.supplierCode) query.supplierCode = { $regex: data.supplierCode, $options: "i" }; // 模糊查询物料
    query.supplierAmount = buildRangeQuery(+data.supplierAmountMin, +data.supplierAmountMax);
    if ([true, false].includes(data.isPayOff)) {
        query.supplierunpaid = data.isPayOff ? 0 : { $gt: 0 }
    }
    // 移除未定义的查询条件
    Object.keys(query).forEach(
        (key) => query[key] === undefined && delete query[key]
    );


    try {
        params.isAll = true
        let supBills = await paginate(supplier, query, params, [
            {
                path: 'product',
                populate: {
                    path: 'pid',
                    model: 'supplierProduct' // 假设 pid 引用的是 supplierProduct 模型
                }
            },
            {
                path: 'supplierOrigin',
                model: 'bill'
            }
        ]);

        response.success(ctx, {
            data: {
                totalAmount: supBills.results.reduce((acc, bill) => acc + (bill.supplierAmount || 0), 0).toFixed(2)
            },
        });
    } catch (err) {
        handleDatabaseError(ctx, err);
    }
});



router.post("/getSupBill", async (ctx, next) => {
    let data = ctx.request.body;
    await supplier.findOne({ _id: data.id }).then((res) => {
        response.success(ctx, { data: res });
    });
});



router.get("/getSupRandomCode", async (ctx, next) => {
    let code;
    let isUnique = false;
    while (!isUnique) {
        code =
            "KFS" +
            dayjs().format("YYYYMMDD") +
            "-" + dayjs().format("HHmmss")

        await supplier.findOne({ supplierCode: code }).then((res) => {
            if (!res) {
                isUnique = true;
            }
        });
    }

    response.success(ctx, { data: code });
});

router.post(
    "/addSupBill",
    validationMiddleware(rulesSchema),
    async (ctx, next) => {
        let data = ctx.request.body;
        data.createTime = dayjs().format('YYYY-MM-DD HH:mm:ss');
        if (data.product.length !== 0) {
            const pidsWithQuantity = data.product.map(e => ({
                pid: e.pid,
                number: e.number,
                price: e.price[0],
                specification: e.specification[0]
            }));
            if (pidsWithQuantity.length === 0) {
                return response.error(ctx, { message: '产品信息不完整' });
            }
            let fdata = easyCopy(data);
            fdata.product = pidsWithQuantity;
            await supplier
                .create(fdata)
                .then(() => {
                    response.success(ctx, {});
                })
                .catch((err) => {
                    console.log(err);
                    response.error(ctx, {});
                });
        } else {
            response.error(ctx, { message: '产品信息不完整' });
        }
    }
);

router.post(
    "/putSupBill",
    validationMiddleware(rulesSchema),
    async (ctx, next) => {
        let data = ctx.request.body;
        data.createTime = dayjs().format('YYYY-MM-DD HH:mm:ss');
        if (data.product.length !== 0) {
            const pidsWithQuantity = data.product.map(e => ({
                pid: e.pid,
                number: e.number,
                price: e.price[0],
                specification: e.specification[0]
            }));
            if (pidsWithQuantity.length === 0) {
                return response.error(ctx, { message: '产品信息不完整' });
            }
            let fdata = easyCopy(data);
            fdata.product = pidsWithQuantity;
            await supplier
                .findOneAndUpdate({ _id: fdata.id }, { $set: fdata })
                .then(() => {
                    response.success(ctx, {});
                })
                .catch((err) => {
                    response.error(ctx, {});
                });
        } else {
            response.error(ctx, { message: '产品信息不完整' });
        }
    }
);

router.post(
    "/delSupBill",
    validationMiddleware(rulesSchema),
    async (ctx, next) => {
        let data = ctx.request.body;
        await supplier.findByIdAndDelete(data.id).then(() => {
            response.success(ctx, {});
        });
    }
);

router.post("/exportData", async (ctx, next) => {
    let data = ctx.request.body;
    let params = ctx.request.query;
    // 动态构建查询条件
    let query = {};
    query.supplierDate = data.ShippingDate
        ? buildRangeQuery(data.ShippingDate[0], data.ShippingDate[1], "time")
        : undefined;
    if (data.product)
        query.product = {
            $elemMatch: {
                pid: data.product,
            }, // 精准匹配产品名称
        };
    if (data.supplierName) query.supplierName = { $regex: data.supplierName, $options: "i" }; // 模糊查询客户名称
    if (data.supplierCode) query.supplierCode = { $regex: data.supplierCode, $options: "i" }; // 模糊查询物料
    query.supplierAmount = buildRangeQuery(+data.supplierAmountMin, +data.supplierAmountMax);
    if ([true, false].includes(data.isPayOff)) {
        query.supplierunpaid = data.isPayOff ? 0 : { $gt: 0 }
    }
    params.isAll=true
    // 移除未定义的查询条件
    Object.keys(query).forEach(
        (key) => query[key] === undefined && delete query[key]
    );

    try {

        // 假设这里从数据库获取要导出的数据
        let suppliers = await paginate(supplier, query, params, [{
            path: 'product',
            populate: {
                path: 'pid',
                model: 'supplierProduct' // 假设 pid 引用的是 supplierProduct 模型
            }
        },
        {
            path: 'supplierOrigin',
            model: 'bill'
        }]);


        const supplierData = suppliers.results.map((item) => ({
            供应商名称: item.supplierName,
            联系方式: item.supplierTel,
            创建时间: item.createTime,
            订单编码: item.supplierCode,
            产品信息: item.product.map((e, i) => {
                return `产品${i + 1}:名称:${e?.pid?.name} 规格:${e?.specification} 数量:${e.number}${e?.pid?.unit}  单价:￥${e.price}`;
            }).join(", "),
            发货情况: item.isSend ? '已发货' : '未发货',
            账单来源: item.supplierOrigin.map((e, i) => {
                return `来源${i + 1}:名称:${e?.name}[${e?.code}]`;
            }).join(", "),
            订单日期: dayjs(item.supplierDate).format("YYYY-MM-DD"),
            开票情况: item.supplierInvoice,
        }));

        // 创建工作簿
        const wb = XLSX.utils.book_new();
        // 创建工作表
        const billWs = XLSX.utils.json_to_sheet(supplierData);
        // 将工作表添加到工作簿
        XLSX.utils.book_append_sheet(wb, billWs, `供应商账单数据`);
        // 生成 Excel 文件
        const excelBuffer = XLSX.write(wb, { bookType: "xlsx", type: "buffer" });

        // 设置响应头
        ctx.set(
            "Content-Type",
            "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"
        );
        ctx.set("Content-Disposition", "attachment; filename=gysexportData.xlsx");
        // 返回 Excel 文件
        ctx.body = excelBuffer;
    } catch (err) {
        console.log(err, "err");
        handleDatabaseError(ctx, err);
    }
});

module.exports = router;
